/**
 * SPDX-FileCopyrightText: 2023-2025 Sangfor Technologies Inc.
 * SPDX-License-Identifier: Mulan PSL v2
 */
<template>
    <div class="dataload-wrap">
        <flow-common-top @roll-back="refreshAIFlow" />
        <load-data-set
            v-if="showLoadSource"
            ref="loadDataSet"
            :source-list="sourceList"
            @submit-datasource="_submitLoadDataSet" />
        <div v-else
             class="dataload-container">
            <div class="preview-operate">
                <!-- 数据源名称 -->
                <page-title
                    :title-name="dataSourceTitle"
                    :small-size="true"
                    class="preview-operate__top-title" />
                <sf-toolbar ref="toolbar">
                    <!-- 只有等于1的时候才可以更新数据集 -->
                    <sf-button
                        class="btn-blank"
                        icon-cls="iconcolony"
                        :default-disabled="disableEditDataSet"
                        @click="_editDataSet">
                        <lang>更换数据集</lang>
                    </sf-button>
                    <sf-button
                        ref="submit"
                        class="creat-button btn-blank"
                        icon-cls="iconzhuzhuangtunormal"
                        @click="_analysisField">
                        <!-- 统计分析获取数据要10s，等出来数据才让其可以点击 -->
                        <!-- 没有步骤时，特征可视化不可点击 -->
                        <lang>统计分析</lang>
                    </sf-button>
                </sf-toolbar>
                <preview-table
                    ref="previewTable"
                    :table-header-list="tableHeaderList"
                    :table-data="previewList" />
                <!-- 无预览结果 -->
            </div>
        </div>
    </div>
</template>
<script>



import PreviewTable from '../components/preview_table.vue';
import pageTitle from 'src/home/mod_cluster/common/page_title/page_title';
import urlAdapter from 'src/home/mod_common/url_adapter';

import loadDataSet from './label_form/load_data_set.vue';


import store from 'src/vuex/store';
let userID = store.state.userId;


const DATASOURCE_LIST_URL = urlAdapter(`user/${userID}/dataSource`);

import parseJson from 'src/util/parse_json.ts';
import { deepClone } from 'src/util/deep_clone';

//统计分析
import AnalysisField from './component/analysis_field.vue';
import trainingUrlAdapter from 'src/home/mod_common/training_url_adapter';

const FLOW_URL = {
    post: trainingUrlAdapter(`user/${userID}/flow`),
    put: trainingUrlAdapter('flow'),
    get: trainingUrlAdapter('flow')
};
import FlowCommonTop from '../components/flow_common_top.vue';
import TRAINING_INFO from '../const.ts';

import FlowOpr from '../components/common/flow_opr.js';

export default {
    name: 'DataLoad',
    components: {
        PreviewTable,
        pageTitle,
        FlowCommonTop,
        loadDataSet
    },
    mixins: [FlowOpr],
    data () {
        return {
            ruleGraphList: [], //图列表
            previewList: [], //预览列表
            tableHeaderList: [], //预览列表表头
            fieldList: [], //字段列表
            dataSourceId: '', //es数据源id
            indexName: '', //es索引
            graphId: '',

            // showDataSourceActive: true,
            fieldBoxList: [], //统计分析list
            dataSourceTitle: '', //数据源title
            dataSourceName: '', //数据源名称
            dataSourceType: '', // 数据源类型
            sourceList: [],
            sourceType: '',
            showLoadSource: true,
            editFlowName: '',
            aiFlowId: '', //ai_flow id
            aiFlowSnapshotId: '', //al_flow 版本id
            graphRule: {},
            columnsList: [],  //特征探索最后步骤的字段
            allColumns: [],  //所有表头字段
            lastColumns:[], //最后表头字段
            nullAIInfo: true,
            editDataSourceFlag: false //是否有编辑数据源操作
        };
    },
    computed: {
        projectId () {
            return this.$route.query.projectId || '';
        },
        aiFlowType () {
            return +this.$route.query.aiFlowType || 0;
        },
        getDataSourceParams () {
            let params = this.ruleGraphList.length ? this.ruleGraphList[0].params : {};
            return params;
        },
        disableEditDataSet () {
            return this.ruleGraphList.length !== 1;
        }
    },
    mounted () {
        this.aiFlowId = this.$route.query.aiFlowId || '';
        this._getDataSetList();
        if (this.isNullObject(this.aiFlowInfo)) {
            this._getAIFlowSnapShot();
        } else {
            this.handleAIFlowInfo(this.aiFlowInfo);
        }
    },
    beforeRouteLeave (to, from, next) {

        //如果有选择数据源但没有点确定的情况
        if (this.showLoadSource) {
            this.saveAiFlowInfo({});
            next(true);
            return false;

            // let ajaxParams = deepClone(this.$refs.loadDataSet.getJsonValue());
            // if (ajaxParams.dataSourceId) {
            //     this.nullAIInfo = false;
            //     this.cacheNullAIFlowInfo(ajaxParams);
            // }
        }

        if (to.name === 'feature_manager' || to.name === 'model_training') {
            next(true);
            return false;
        };

        if (this.nullAIInfo) {
            this.saveAiFlowInfo({});
            next(true);
        } else {

            //数据源添加后，保存了aiflowname名称，但此时没有编辑ai_flow名称，因为已经保存了，所以不弹窗。
            this.$confirm({
                title: _('提示'),
                msg: _('AI FLOW 尚未保存，是否离开当前页面？'),
                autoDestroy: true,
                autoClose: true,
                buttons: [{
                    cls: 'visual-save-exit-btn',
                    actionName: 'leave',
                    loading: true,
                    text:  _('直接离开')
                }, {
                    actionName: 'submit',
                    loading: true,
                    text:_('保存并离开')
                }, {
                    actionName: 'cancel',
                    text: '取消'
                }],
                leave: () => {
                    this.saveAiFlowInfo({});
                    next(true);
                },
                submit: () => {
                    this._saveGraph().then(() => {
                        this.saveAiFlowInfo({});
                        next(true);
                    });
                }
            });
        }
    },

    methods: {
        refreshAIFlow (data) {
            this.nullAIInfo = false;
            this.editDataSourceFlag = false;
            this.saveAiFlowInfo(data);
            this.handleAIFlowInfo(data);
        },
        

        handleAIFlowInfo (data) {
            let { graphInfo } = data;
            if (!graphInfo) {
                this.showLoadSource = true;
                return false;
            };
            let lastColumns = parseJson(graphInfo.lastColumns);
            if (lastColumns && !lastColumns.length) {
                this.showLoadSource = true;
                let dataSourceParams = {
                    csvFilepath:graphInfo.csvFilepath,
                    dataSourceId:graphInfo.dataSourceId,
                    index:graphInfo.index,
                    sourceType:graphInfo.sourceType,
                    url:graphInfo.url
                };
                this.$refs.loadDataSet.setJsonValue(dataSourceParams);
                return false;
            }
            this.showLoadSource = false;
            let dataSourceInfo = parseJson(graphInfo.graphRule)[0];
            let tableName = dataSourceInfo.params.index;
            if (graphInfo.dataSourceType === 'csv') {
                this.dataSourceTitle = `数据集名称：${graphInfo.dataSourceName}`;
            } else {
                 if (tableName) {
                    this.dataSourceTitle = `数据集名称：${graphInfo.dataSourceName}（${tableName}）`;
                } else {
                    this.dataSourceTitle = `数据集名称：${graphInfo.dataSourceName}`;
                }
            }
            this.ruleGraphList = parseJson(graphInfo.graphRule);

            // let analysisParams = dataSourceInfo.params;
            // this._getAnalysis(analysisParams);

            //说明肯定存在数据源
            if (this.ruleGraphList.length > 0) {
                let list = deepClone(this.ruleGraphList).slice(0, 1);
                this._dataPreview(list);
            }
        },

        //获取图规则
        async _getAIFlowSnapShot () {
            let getSnapShotURL = `${FLOW_URL.get}/${this.aiFlowId}`;
            this.$mask();
            let jsonData = await this.$ajax.get(getSnapShotURL);

            this.$unmask();
            let { success, msg, data } = jsonData;
            if (!success) {
                this.$showErr(msg || _('加载数据失败'));
                return;
            };
            this.handleAIFlowInfo(data);
            if (!data.graphInfo) {
                this.nullAIInfo = true;
                return false;
            }
            this.saveAiFlowInfo(data);
        },

        //先预览，预览成功后才能保存
        async _dataPreview (list, isSaveInfo = false) {
            this.showLoadSource = false;
            this.nullAIInfo = false;

            // 0代表获取数据源算子
            let stepData = list;
            let params = {
                ruleGraph: {
                    operators:stepData
                },
                dataSourceName:this.dataSourceName,
                dataSourceId:this.dataSourceId,
                projectId: this.projectId
            };

            let previewURL = urlAdapter('feature/graph/sql');

            //目的是让整个项目都未遮罩层，因为请求要3-4s才有数据，防止用户点击其它项目产生bug.
            this.$mask();
            let req;
            this.$once('hook:beforeDestroy', () => {
                req.abort();
            });
            let jsonData = await this.$ajax.post(previewURL, params, {
                before: (request) => {
                    req = request;
                }
            });
            this.$unmask();
            if (!jsonData) {
                return;
            }
            let { success, msg, data } = jsonData;
            if (!success) {
                this.$showErr(msg || _('加载数据失败'));
                return;
            }

            let columns = data.columns;
            let ruleGraph = data.graphRule.ruleGraph;

            //将预览的每个columns字段保存起来。

            //读取表格内容
            try {


                //获取数据源
                let headerList = [];
                for (let i in columns) {
                    if (Object.prototype.hasOwnProperty.call(columns, i)) {
                        headerList.push({
                            name: i
                        });
                    }
                }

                this.tableHeaderList = headerList;

                //临时缓存AIFlowInfo;
                if (isSaveInfo) {
                    this.lastColumns = columns;
                    this.allColumns = ruleGraph.firstColumns;

                    let jsons = ruleGraph.operators[0];
                    this.isNullObject(this.aiFlowInfo) ? this.cacheNullAIFlowInfo(jsons) : this.cacheAIFlowInfo();
                }
                this.previewList = JSON.parse(data.result);
            } catch (e) {
                this.previewList = [];
                columns = [];
            };

        },

        //保存步骤
        async _saveGraph () {
            const SAVEURL = `${FLOW_URL.put}/${this.aiFlowId}/snapshot`;
            let params = this.aiFlowInfo;
            this.$mask();
            let jsonData = await this.$ajax.put(SAVEURL, params);
            let { success, msg } = jsonData;
            this.$unmask();
            if (!success) {
                this.$showErr(msg || _('加载数据失败'));
                return;
            };
        },
        _createAnalysisFieldFormWin () {
            if (!this.analysisFieldFormWin) {
                this.analysisFieldFormWin = this.$modal(AnalysisField, {
                    autoDestory: true
                });
            }
            return this.analysisFieldFormWin;
        },

        //统计分析
        async _analysisField () {
            if (!this.analysisFieldFormWin) {
                this._createAnalysisFieldFormWin();
            }
            let formWin = this._createAnalysisFieldFormWin();
            let params = this.ruleGraphList[0].params;
            let getGraphURL = urlAdapter(`feature/graph/analysis`);
            this.$mask();
            let jsonData = await this.$ajax.get(getGraphURL, params);
            let { success, msg, data } = jsonData;
            if (!success) {
                this.$showErr(msg || _('加载数据失败'));
                return;
            }
            this.$unmask();
            this.fieldBoxList = data;
            formWin.open({
                reset: true,
                title: _('统计分析'),
                data: {
                    fieldBoxList: this.fieldBoxList,
                    fieldCloneBoxList: this.fieldBoxList,
                    fieldDatailType: this.fieldBoxList[0].dtype
                },
                buttons: [{
                    cls: 'btn-default',
                    text: '关闭',
                    actionName: 'cancel'
                }],
                cancel: () => {
                    formWin.hide();
                }
            });
        },

        
        //获取数据源list
        async _getDataSetList () {
            let jsonData = await this.$ajax.get(DATASOURCE_LIST_URL);
            let { success, msg, data } = jsonData;
            if (!success) {
                return this.$showErr(msg || _('加载数据失败'));
            }
            let list = [];
            data.forEach(item => {
                list.push({
                    label: item.name,
                    value: item.id,
                    type: item.type,
                    url:item.url
                });
            });
            this.sourceList = list;
        },
        _operateDataSet (ele) {
             let vm = this;
            let ajaxParams = ele.getJsonValue();

            //肯定是没选择数据源;
            if (!ajaxParams.csvFilepath && !ajaxParams.dataSourceId) {
                this.$warn(_('请选择数据源'), { autoHide: true });
                return false;
            }
            let otherParams = ele.getOtherJsonValue();
            this.dataSourceName = otherParams.dataSourceName;
            this.dataSourceId = ajaxParams.dataSourceId;
            this.dataSourceType = otherParams.dataSourceType;
            let ruleGraphList = [{
                'type': 'datasource',
                'id': 1,
                'params': ajaxParams
            }];
            if (otherParams.dataSourceType === 'csv') {
                this.dataSourceTitle = `数据集名称：${this.dataSourceName}`;
            } else {
                if (ajaxParams.index) {
                    this.dataSourceTitle = `数据集名称：${otherParams.dataSourceName}（${ajaxParams.index}）`;
                } else {
                    this.dataSourceTitle = `数据集名称：${otherParams.dataSourceName}`;
                }
            }
            this.ruleGraphList = ruleGraphList;

            // vm._getAnalysis(ajaxParams);
            vm._dataPreview(ruleGraphList, true);
        },
        _submitLoadDataSet () {
           this._operateDataSet(this.$refs.loadDataSet);
        },

        _submitEditDataSet () {
            this._operateDataSet(this.editDataSetFormWin.formRoot);

            //关闭数据集弹窗
            this.editDataSetFormWin && this.editDataSetFormWin.hide();

            //目的是将选中的标签数据和训练数据清空，因为有编辑修改数据集。
            this.editDataSourceFlag = true;
        },

        //编辑数据集
        _createEditDataSetFormWin () {
            this.editDataSetFormWin = this.$modal(loadDataSet, {
                autoDestory: true,
                props:{
                    sourceList:this.sourceList,
                    isEdit:true
                }
            });
            return this.editDataSetFormWin;
        },

        //添加数据集
        async _editDataSet () {

            //有了新增步骤后，不能再编辑数据源
            if (this.ruleGraphList.length > 1) {
                return this.$showErr(_('已有特征处理步骤，不能编辑数据源集'));
            }
            let editDataSetFormWin = this._createEditDataSetFormWin();
            editDataSetFormWin.formRoot.setJsonValue(this.getDataSourceParams);

            // let typeList = this.sourceList.filter(item => item.value === this.getDataSourceParams.dataSourceId);
            // let type = typeList.length > 0 ? typeList[0].type : '';
            let activeIndex = this.getDataSourceParams.csvFilepath ? 0 : 1;
            editDataSetFormWin.open({
                title: _('编辑数据集'),
                data: {
                    activeIndex

                    // sourceType: type
                },
                submit: () => {
                    this._submitEditDataSet();
                }
            });
        },
        cacheAIFlowInfo () {
            let info = deepClone(this.aiFlowInfo);
            info.graphInfo.graphRule = JSON.stringify(this.ruleGraphList);
            info.graphInfo.lastColumns = JSON.stringify(Object.keys(this.lastColumns));
            info.graphInfo.allColumns = JSON.stringify(Object.keys(this.lastColumns));
            info.graphInfo.dataSourceName = this.dataSourceName;
            info.graphInfo.dataSourceType = this.dataSourceType;
            info.graphInfo.dataSourceId = this.dataSourceId;
            info.dataSourceId = this.dataSourceId;
            info.graphInfo.dagCommand.operators = this.ruleGraphList;
            info.trainingInfo.dagCommand.operators = this.ruleGraphList;

            //如果有编辑数据源操作，需要将选择的标签数据和训练数据清空；
            if (this.editDataSourceFlag) {
                info.trainingInfo.lastColumns = '[]';
                info.trainingInfo.trainColumns = '[]';
                info.trainingInfo.labelColumns = '[]';
            }
            this.saveAiFlowInfo(info);
        },
        cacheNullAIFlowInfo (jsons) {
            let {params} = jsons;
            if (!params) {
                params = jsons;
            }
            let info = {
                aiFlowId: this.aiFlowId,
                projectId: this.projectId,
                dataSourceId: params.dataSourceId,
                graphInfo: {
                    dataSourceId:params.dataSourceId,
                    index:params.index,
                    dataSourceName: this.dataSourceName,
                    dataSourceType: this.dataSourceType,
                    graphRule: JSON.stringify(this.ruleGraphList) || '',
                    lastColumns:JSON.stringify(Object.keys(this.lastColumns)),
                    allColumns: JSON.stringify(Object.keys(this.allColumns)),
                    dagCommand:{
                        operators:this.ruleGraphList
                    }
                },
                trainingInfo: TRAINING_INFO,
                algorithmId: '',
                version: null,
                userId:userID
            };
            info.trainingInfo.dagCommand.operators = this.ruleGraphList;
            this.saveAiFlowInfo(info);
        },
      

        //修改路由，给刷新使用
        _editRouter () {
            let query = JSON.parse(JSON.stringify(this.$route.query));
            query.aiFlowId = this.aiFlowId;
            this.$router.push({ path: this.$route.path, query });
        }

    }

};
</script>
<style lang="less">
.dataload-wrap {
    height: 100%;
}
.dataload-container {
    display: flex;
    flex: 1;
    height: calc(100% - 156px);
    overflow: hidden;
    .preview-operate {
        // margin-right: 10px;
        margin: 8px;
        /* width: 1350px; */
        flex: 1;
        width: calc(100% - 242px);
        border: 1px solid #dee3ed;
        .preview-operate__top-title {
            margin: 0;
            padding-left: 12px;
        }
        .sfv-toolbar_inner {
            border-bottom: none;
        }
        /* width: calc(100% - 500px); */
    }
}
</style>
